home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Mac Power 1997 December
/
MACPOWER-1997-12.ISO.7z
/
MACPOWER-1997-12.ISO
/
MacPowerオリジナル
/
キョービのプログラマー
/
Flash Trash src
/
Flash Trash.c
next >
Wrap
C/C++ Source or Header
|
1997-10-06
|
7KB
|
240 lines
#include <A4Stuff.h>
#include <SetupA4.h>
#include <Files.h>
#include <Traps.h>
#include <Sound.h>
/*------------- main routine -------------*/
void main(void);
/*------------- initialize routines -------------*/
Boolean load_resources(void);
Handle load_one_resource(ResType res_type, short res_id);
void install_trap(void);
/*------------- my GetResource routine -------------*/
typedef pascal Handle (*GetResourceProc)(ResType res_type, short res_id);
typedef pascal Handle (*Get1ResourceProc)(ResType res_type, short res_id);
pascal Handle my_GetResource(ResType res_type, short res_id);
pascal Handle my_Get1Resource(ResType res_type, short res_id);
void check_and_replace_icon(ResType res_type, short res_id, Handle h);
void copy_handle(Handle src, Handle dst);
/*------------- flush sound routine -------------*/
void setup_flush_sound(void);
void snd_stop(void);
void start_flush_sound(void);
/*------------- my PBHDelete routine -------------*/
OSErr my_pbhdelete(void);
OSErr asm call_original_pbhdelete(long pb, long call_addr);
long asm get_a0(void);
void asm set_a0(long pb);
/*------------- inline asm -------------*/
void push_d0_and_a0(void) TWOWORDINLINE(0x48E7, 0x8080); // MOVEM.L D0/A0,-(A7)
void pop_d0_and_a0(void) TWOWORDINLINE(0x4CDF, 0x0101); // MOVEM.L (A7)+,D0/A0
/*------------- global -------------*/
long original_pbhdelete;
GetResourceProc old_GetResource;
Get1ResourceProc old_Get1Resource;
Handle empty_icl4, empty_icl8, empty_ICN, empty_ics, empty_ics4, empty_ics8;
Handle fat_icl4, fat_icl8, fat_ICN, fat_ics, fat_ics4, fat_ics8;
Handle flush_sound;
SndChannelPtr snd_chan_ptr;
Boolean snd_chan_ready;
void main(void)
{
long old_A4;
old_A4 = SetCurrentA4();
RememberA4();
if(load_resources()) {
install_trap();
setup_flush_sound();
ShowInitIcon(128, -1);
} else {
ShowInitIcon(129, -1);
}
SetA4(old_A4);
}
/*------------- initialize routines -------------*/
Boolean load_resources(void)
{
if(load_one_resource('INIT', 0) == nil) return false;
if((empty_icl4 = load_one_resource('icl4', 130)) == nil) return false;
if((empty_icl8 = load_one_resource('icl8', 130)) == nil) return false;
if((empty_ICN = load_one_resource('ICN#', 130)) == nil) return false;
if((empty_ics = load_one_resource('ics#', 130)) == nil) return false;
if((empty_ics4 = load_one_resource('ics4', 130)) == nil) return false;
if((empty_ics8 = load_one_resource('ics8', 130)) == nil) return false;
if((fat_icl4 = load_one_resource('icl4', 131)) == nil) return false;
if((fat_icl8 = load_one_resource('icl8', 131)) == nil) return false;
if((fat_ICN = load_one_resource('ICN#', 131)) == nil) return false;
if((fat_ics = load_one_resource('ics#', 131)) == nil) return false;
if((fat_ics4 = load_one_resource('ics4', 131)) == nil) return false;
if((fat_ics8 = load_one_resource('ics8', 131)) == nil) return false;
return true;
}
Handle load_one_resource(ResType res_type, short res_id)
{
Handle h;
h = Get1Resource(res_type, res_id);
if(h) {
HNoPurge(h);
DetachResource(h);
MoveHHi(h);
HLock(h);
}
return h;
}
void install_trap(void)
{
original_pbhdelete = (long)GetOSTrapAddress(_HDelete);
SetOSTrapAddress((UniversalProcPtr)my_pbhdelete, _HDelete);
old_GetResource = (GetResourceProc)GetToolTrapAddress(_GetResource);
SetToolTrapAddress((UniversalProcPtr)my_GetResource, _GetResource);
old_Get1Resource = (Get1ResourceProc)GetToolTrapAddress(_Get1Resource);
SetToolTrapAddress((UniversalProcPtr)my_Get1Resource, _Get1Resource);
}
/*------------- my GetResource routine -------------*/
pascal Handle my_GetResource(ResType res_type, short res_id)
{
Handle h = nil;
long oldA4;
oldA4 = SetUpA4();
h = old_GetResource(res_type, res_id);
check_and_replace_icon(res_type, res_id, h);
RestoreA4(oldA4);
return h;
}
pascal Handle my_Get1Resource(ResType res_type, short res_id)
{
Handle h = nil;
long oldA4;
oldA4 = SetUpA4();
h = old_Get1Resource(res_type, res_id);
check_and_replace_icon(res_type, res_id, h);
RestoreA4(oldA4);
return h;
}
void check_and_replace_icon(ResType res_type, short res_id, Handle h)
{
if(res_id == -3993) {
if(res_type == 'icl4') copy_handle(empty_icl4, h);
if(res_type == 'icl8') copy_handle(empty_icl8, h);
if(res_type == 'ICN#') copy_handle(empty_ICN, h);
if(res_type == 'ics#') copy_handle(empty_ics, h);
if(res_type == 'ics4') copy_handle(empty_ics4, h);
if(res_type == 'ics8') copy_handle(empty_ics8, h);
}
if(res_id == -3984) {
if(res_type == 'icl4') copy_handle(fat_icl4, h);
if(res_type == 'icl8') copy_handle(fat_icl8, h);
if(res_type == 'ICN#') copy_handle(fat_ICN, h);
if(res_type == 'ics#') copy_handle(fat_ics, h);
if(res_type == 'ics4') copy_handle(fat_ics4, h);
if(res_type == 'ics8') copy_handle(fat_ics8, h);
}
}
void copy_handle(Handle src, Handle dst)
{
long src_size, dst_size;
if(src && dst) {
src_size = GetHandleSize(src);
dst_size = GetHandleSize(dst);
if(src_size == dst_size)
BlockMove(*src, *dst, src_size);
}
}
/*------------- flush sound routine -------------*/
void setup_flush_sound(void)
{
flush_sound = load_one_resource('snd ', 128);
snd_chan_ptr = nil;
snd_chan_ready = false;
snd_chan_ptr = (SndChannelPtr)NewPtrSysClear(sizeof(SndChannel));
if(snd_chan_ptr)
snd_chan_ptr->qLength = stdQLength;
}
void snd_stop(void)
{
if(snd_chan_ready) {
SndDisposeChannel(snd_chan_ptr, true);
snd_chan_ptr->qLength = stdQLength;
snd_chan_ready = false;
}
}
void start_flush_sound(void)
{
if(snd_chan_ready)
snd_stop();
if(flush_sound)
if(SndNewChannel(&snd_chan_ptr, sampledSynth, 0, nil) == 0) {
snd_chan_ready = true;
SndPlay(snd_chan_ptr, (SndListHandle)flush_sound, true);
}
}
/*------------- my PBHDelete routine -------------*/
OSErr my_pbhdelete(void)
{
HFileParamPtr pb;
short err;
long old_A4;
short trash_vrefnum;
long trash_dirid;
push_d0_and_a0(); // save d0 and a0 into stack
old_A4 = SetUpA4(); // setup global base
pop_d0_and_a0(); // load d0 and a0 into stack
pb = (HFileParamPtr)get_a0(); // get a0(ParamBlockPtr)
err = call_original_pbhdelete((long)pb, original_pbhdelete); // call original trap
pb = (HFileParamPtr)get_a0();
if(err == 0)
if(FindFolder(pb->ioVRefNum, kTrashFolderType, false, &trash_vrefnum, &trash_dirid) == 0)
if(trash_dirid == pb->ioDirID)
start_flush_sound();
set_a0((long)pb); // re load A0 for safe
RestoreA4(old_A4);
return err;
}
OSErr asm call_original_pbhdelete(long pb, long call_addr)
{
fralloc +
movem.l D1-D7/A1-A6, -(A7)
move.l pb, a0
move.l call_addr, a1
jsr (a1)
movem.l (A7)+,D1-D7/A1-A6
frfree
rts
}
long asm get_a0(void)
{
move.l a0, d0
rts
}
void asm set_a0(long pb)
{
fralloc +
move.l pb, a0
frfree
rts
}